// @Author EthanScriptOn
// @Desc
package detect

import (
	"fmt"
	"gitee.com/fatzeng/srf_switch_basic_components/switch_log"
	"gitee.com/fatzeng/srf_switch_basic_components/util"
)

type ResourceMonitor struct {
	Name            string
	IsTimeConsuming bool
	Checker         ResourceCheck
	Recover         ResourceRecover
	Monitor         MonitorFunction
}

func GenerateResourceMonitor(name string, isTimeConsuming bool, checker ResourceCheck, recover ResourceRecover, monitor MonitorFunction) *ResourceMonitor {
	return &ResourceMonitor{
		Name:            name,
		IsTimeConsuming: isTimeConsuming,
		Checker:         checker,
		Recover:         recover,
		Monitor:         monitor,
	}
}

func (rm *ResourceMonitor) IsValid() bool {
	return rm.Name != "" && rm.Checker != nil && rm.Recover != nil
}

type ResourceCheck func() (isInvalid bool)

type ResourceRecover func() (err error)

type MonitorFunction func(monitor *ResourceMonitor) error

var MonitorFunctionInstance = func(rm *ResourceMonitor) (err error) {
	defer util.HandleErr(&err)
	if rm.Checker() {
		switch_log.Logger().Info(fmt.Sprintf("Resource '%s' check failed, attempting detect...", rm.Name))
		if recoverErr := rm.Recover(); recoverErr != nil {
			switch_log.Logger().Error(fmt.Sprintf("Failed to recover resource '%s': %v", rm.Name, recoverErr))
			err = recoverErr
			return
		}
		switch_log.Logger().Info(fmt.Sprintf("Resource '%s' recovered successfully", rm.Name))
		return
	}
	switch_log.Logger().Info(fmt.Sprintf("Resource '%s' is healthy: ", rm.Name))
	return
}
